2 * JavaScript for Special:Preferences: Tab navigation.
6 var tabs
, previousTab
, switchingNoHash
;
8 // Make sure the accessibility tip is focussable so that keyboard users take notice,
9 // but hide it by default to reduce visual clutter.
10 // Make sure it becomes visible when focused.
11 $( '<div>' ).addClass( 'mw-navigation-hint' )
12 .text( mw
.msg( 'prefs-tabs-navigation-hint' ) )
17 .insertBefore( '.mw-htmlform-ooui-wrapper' );
19 tabs
= OO
.ui
.infuse( $( '.mw-prefs-tabs' ) );
21 tabs
.$element
.addClass( 'mw-prefs-tabs-infused' );
23 function enhancePanel( panel
) {
24 if ( !panel
.$element
.data( 'mw-section-infused' ) ) {
25 panel
.$element
.removeClass( 'mw-htmlform-autoinfuse-lazy' );
26 mw
.hook( 'htmlform.enhance' ).fire( panel
.$element
);
27 panel
.$element
.data( 'mw-section-infused', true );
31 function onTabPanelSet( panel
) {
32 var scrollTop
, active
;
34 if ( switchingNoHash
) {
37 // Handle hash manually to prevent jumping,
38 // therefore save and restore scrollTop to prevent jumping.
39 scrollTop
= $( window
).scrollTop();
40 // Changing the hash apparently causes keyboard focus to be lost?
41 // Save and restore it. This makes no sense though.
42 active
= document
.activeElement
;
43 location
.hash
= '#' + panel
.getName();
47 $( window
).scrollTop( scrollTop
);
50 tabs
.on( 'set', onTabPanelSet
);
54 * @param {string} name The name of a tab
55 * @param {boolean} [noHash] A hash will be set according to the current
56 * open section. Use this flag to suppress this.
58 function switchPrefTab( name
, noHash
) {
60 switchingNoHash
= true;
62 tabs
.setTabPanel( name
);
63 enhancePanel( tabs
.getCurrentTabPanel() );
65 switchingNoHash
= false;
69 // Jump to correct section as indicated by the hash.
70 // This function is called onload and onhashchange.
71 function detectHash() {
72 var hash
= location
.hash
,
73 matchedElement
, parentSection
;
74 if ( hash
.match( /^#mw-prefsection-[\w]+$/ ) ) {
75 mw
.storage
.session
.remove( 'mwpreferences-prevTab' );
76 switchPrefTab( hash
.slice( 1 ) );
77 } else if ( hash
.match( /^#mw-[\w-]+$/ ) ) {
78 matchedElement
= document
.getElementById( hash
.slice( 1 ) );
79 parentSection
= $( matchedElement
).parent().closest( '[id^="mw-prefsection-"]' );
80 if ( parentSection
.length
) {
81 mw
.storage
.session
.remove( 'mwpreferences-prevTab' );
82 // Switch to proper tab and scroll to selected item.
83 switchPrefTab( parentSection
.attr( 'id' ), true );
84 matchedElement
.scrollIntoView();
89 $( window
).on( 'hashchange', function () {
90 var hash
= location
.hash
;
91 if ( hash
.match( /^#mw-[\w-]+/ ) ) {
93 } else if ( hash
=== '' ) {
94 switchPrefTab( 'mw-prefsection-personal', true );
97 // Run the function immediately to select the proper tab on startup.
98 .trigger( 'hashchange' );
100 // Restore the active tab after saving the preferences
101 previousTab
= mw
.storage
.session
.get( 'mwpreferences-prevTab' );
103 switchPrefTab( previousTab
, true );
104 // Deleting the key, the tab states should be reset until we press Save
105 mw
.storage
.session
.remove( 'mwpreferences-prevTab' );
108 $( '#mw-prefs-form' ).on( 'submit', function () {
109 var value
= tabs
.getCurrentTabPanelName();
110 mw
.storage
.session
.set( 'mwpreferences-prevTab', value
);